import { Prefab, resources } from "cc";
import { Defeat } from "./popup.defeat";
import { Free } from "./popup.free";
import { FreeCache } from "./popup.free.cache";
import { FreeConfirm } from "./popup.free.confirm";
import { FreeInfo } from "./popup.free.info";
import { FreeSuccess } from "./popup.free.success";
import { FruitDiamond } from "./popup.fruit.diamond";
import { FruitSpecial } from "./popup.fruit.special";
import { Prop } from "./popup.prop";
import { Rank } from "./popup.rank";
import { Resurgence } from "./popup.resurgence";
import { Setting } from "./popup.setting";
import { Task } from "./popup.task";
import { ppTreasureBox } from "./popup.treasurebox";
import { Victory } from "./popup.victory";
import { Wait } from "./popup.wait";

export enum EPopup {
	DEFEAT,
	FREE_INFO,
	FREE,
	FREE_CACHE,
	FREE_CONFIRM,
	FREE_SUCCESS,
	FRUIT_DIAMOND,
	FRUIT_SPECIAL,
	TREASUREBOX,
	PROP,
	RANK,
	RESURGENCE,
	SETTING,
	TASK,
	VICTORY,
	WAIT,
}

const CONFIG = {
	[EPopup.DEFEAT]: {
		component: Defeat,
		path: 'defeat',
		script: './popup.defeat.ts',
		prefab: null
	},
	[EPopup.FREE_INFO]: {
		component: FreeInfo,
		path: 'free-info',
		script: './popup.free.info.ts',
		prefab: null
	},
	[EPopup.FREE]: {
		component: Free,
		path: 'free',
		script: './popup.free.ts',
		prefab: null
	},
	[EPopup.FREE_CACHE]: {
		component: FreeCache,
		path: 'free-cache',
		script: './popup.free.cache.ts',
		prefab: null
	},
	[EPopup.FREE_CONFIRM]: {
		component: FreeConfirm,
		path: 'free-confirm',
		script: './popup.free.confirm.ts',
		prefab: null
	},
	[EPopup.FREE_SUCCESS]: {
		component: FreeSuccess,
		path: 'free-success',
		script: './popup.free.success.ts',
		prefab: null
	},
	[EPopup.FRUIT_DIAMOND]: {
		component: FruitDiamond,
		path: 'fruit-diamond',
		script: './popup.fruit.diamond.ts',
		prefab: null
	},
	[EPopup.FRUIT_SPECIAL]: {
		component: FruitSpecial,
		path: 'fruit-special',
		script: './popup.fruit.special.ts',
		prefab: null
	},
	[EPopup.TREASUREBOX]: {
		component: ppTreasureBox,
		path: 'treasure-box',
		script: './popup.treasurebox.ts',
		prefab: null
	},
	[EPopup.PROP]: {
		component: Prop,
		path: 'prop',
		script: './popup.prop.ts',
		prefab: null
	},
	[EPopup.RANK]: {
		component: Rank,
		path: 'rank',
		script: './popup.rank.ts',
		prefab: null
	},
	[EPopup.RESURGENCE]: {
		component: Resurgence,
		path: 'resurgence',
		script: './popup.resurgence.ts',
		prefab: null
	},
	[EPopup.SETTING]: {
		component: Setting,
		path: 'setting',
		script: './popup.setting.ts',
		prefab: null
	},
	[EPopup.TASK]: {
		component: Task,
		path: 'task',
		script: './popup.task.ts',
		prefab: null
	},
	[EPopup.VICTORY]: {
		component: Victory,
		path: 'victory',
		script: './popup.victory.ts',
		prefab: null
	},
	[EPopup.WAIT]: {
		component: Wait,
		path: 'wait',
		script: './popup.wait.ts',
		prefab: null
	},
}

Reflect.ownKeys(CONFIG).forEach(key=>{
	let conf = CONFIG[key];
	conf.path = 'prefab/pop-up/' + conf.path;
});

export async function GetPopPrefab(p: EPopup): Promise<Prefab> {

	let conf = CONFIG[p];

	if(!conf.prefab){
		conf.prefab = await mtec.cc.loadResAsync(conf.path, Prefab, resources);
	}

	return conf.prefab;
}

export async function GetPopComponent<P extends EPopup>(p: P): Promise<(typeof CONFIG)[P]['component']> {
	let conf = CONFIG[p];
	if(!conf.component){
		conf.component = await import(conf.script).then(m=>m.default);
	}

	return conf.component;
}

export type PopCtor<P extends EPopup> = typeof CONFIG[P]['component'];

export type PopIns<P extends EPopup> = InstanceType<PopCtor<P>>;

export type PopParams<P extends EPopup> = Parameters<PopIns<P>['onShow']>;

export type PopReturn<P extends EPopup> = Awaited<ReturnType<PopIns<P>['show']>>;